package com.example.leetcode.juc;

import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

//class H2O {
//
//    CyclicBarrier barrier = new CyclicBarrier(3);
//    Semaphore semaphore1 = new Semaphore(2);
//    Semaphore semaphore2 = new Semaphore(1);
//
//    public H2O() {
//
//    }
//
//    public void hydrogen(Runnable releaseHydrogen) throws InterruptedException {
//        semaphore1.acquire();
//        try {
//            barrier.await();
//        } catch (BrokenBarrierException e) {
//            throw new RuntimeException(e);
//        }
//        // releaseHydrogen.run() outputs "H". Do not change or remove this line.
//        releaseHydrogen.run();
//        semaphore1.release();
//    }
//
//    public void oxygen(Runnable releaseOxygen) throws InterruptedException {
//        semaphore2.acquire();
//        try {
//            barrier.await();
//        } catch (BrokenBarrierException e) {
//            throw new RuntimeException(e);
//        }
//        // releaseOxygen.run() outputs "O". Do not change or remove this line.
//        releaseOxygen.run();
//        semaphore2.release();
//    }
//}


//class H2O {
//
//    int state1 = 0;
//    int state2 = 0;
//    ReentrantLock lock = new ReentrantLock();
//    // 此处也可以只使用一个Condition队列
//    Condition condition1 = lock.newCondition();
//    Condition condition2 = lock.newCondition();
//
//    public H2O() {
//        state1 = 0;
//        state2 = 0;
//    }
//
//    public void hydrogen(Runnable releaseHydrogen) throws InterruptedException {
//        lock.lock();
//        while (state1 >= 2) {
//            condition1.await();
//        }
//        state1++;
//        // releaseHydrogen.run() outputs "H". Do not change or remove this line.
//        releaseHydrogen.run();
//        if(state1 == 2 && state2 == 1){
//            state1 = 0;
//            state2 = 0;
//        }
//        condition1.signalAll();
//        condition2.signalAll();
//        lock.unlock();
//    }
//
//    public void oxygen(Runnable releaseOxygen) throws InterruptedException {
//        lock.lock();
//        while (state2 >= 1) {
//            condition2.await();
//        }
//        state2++;
//        // releaseOxygen.run() outputs "O". Do not change or remove this line.
//        releaseOxygen.run();
//        if(state1 == 2 && state2 == 1){
//            state1 = 0;
//            state2 = 0;
//        }
//        condition1.signalAll();
//        condition2.signalAll();
//        lock.unlock();
//    }
//}


//class H2O {
//
//    Semaphore semaphore1 = new Semaphore(2);
//    Semaphore semaphore2 = new Semaphore(0);
//
//    public H2O() {
//
//    }
//
//    public void hydrogen(Runnable releaseHydrogen) throws InterruptedException {
//        semaphore1.acquire();
//        // releaseHydrogen.run() outputs "H". Do not change or remove this line.
//        releaseHydrogen.run();
//        semaphore2.release();
//    }
//
//    public void oxygen(Runnable releaseOxygen) throws InterruptedException {
//        semaphore2.acquire(2);
//        // releaseOxygen.run() outputs "O". Do not change or remove this line.
//        releaseOxygen.run();
//        semaphore1.release(2);
//    }
//}


class H2O {

    public H2O() {

    }

    public void hydrogen(Runnable releaseHydrogen) throws InterruptedException {

        // releaseHydrogen.run() outputs "H". Do not change or remove this line.
        releaseHydrogen.run();

    }

    public void oxygen(Runnable releaseOxygen) throws InterruptedException {

        // releaseOxygen.run() outputs "O". Do not change or remove this line.
        releaseOxygen.run();

    }
}

public class leetcode1117 {
    public static void main(String[] args) {
        String str = "OOHHHH";
        test(str);

        String str1 = "HOH";
//        test(str1);
    }

    private static void test(String str) {
        ExecutorService executorService = Executors.newFixedThreadPool(10);
        H2O h2O = new H2O();
        for (int i = 0; i < str.length(); i++) {
            Runnable task;
            if (str.charAt(i) == 'H') {
                task = new Runnable() {
                    @Override
                    public void run() {
                        try {
                            h2O.hydrogen(new Runnable() {
                                @Override
                                public void run() {
                                    System.out.print("H");
                                }
                            });
                        } catch (Exception e) {
                            throw new RuntimeException(e);
                        }
                    }
                };
            } else {
                task = new Runnable() {
                    @Override
                    public void run() {
                        try {
                            h2O.oxygen(new Runnable() {
                                @Override
                                public void run() {
                                    System.out.print("O");
                                }
                            });
                        } catch (Exception e) {
                            throw new RuntimeException(e);
                        }
                    }
                };
            }
            executorService.execute(task);
        }
        executorService.shutdown();
    }
}
